package com.java.module.generator.util;

import java.util.Arrays;

import org.apache.commons.lang3.RegExUtils;

import com.java.common.constant.ProjectConstants;
import com.java.common.utils.StringUtils;
import com.java.module.generator.domain.GeneratorTable;
import com.java.module.generator.domain.GeneratorTableColumn;
import com.java.module.generator.util.constant.GeneratorConstants;
import com.java.module.generator.util.constant.GeneratorConstants.ColumnSuffix;

/**
 * 代码生成器 工具类
 * 
 * @author Administrator
 */
public class GeneratorUtils {

    private static final String COMMA = ",";

    private static final String[] PARENTHESES = { "(", ")" };

    /**
     * 初始化表信息
     */
    public static void initTable(GeneratorTable genTable, String operName) {
        String tableName = genTable.getTableName();
        String moduleName = getModuleName(tableName);
        String modulePackage = ProjectConstants.MODULE_PACKAGE + "." + moduleName;
        String author = "Administrator";
        genTable.setClassName(convertClassName(tableName));
        genTable.setPackageName(modulePackage);
        genTable.setModuleName(moduleName);
        genTable.setBusinessName(getBusinessName(tableName));
        genTable.setFunctionName(replaceText(genTable.getTableComment()));
        genTable.setFunctionAuthor(author);
        genTable.setCreateBy(operName);
    }

    /**
     * 初始化列属性字段
     */
    public static void initColumnField(GeneratorTableColumn column, GeneratorTable table) {
        String dataType = getDbType(column.getColumnType());
        String columnName = column.getColumnName();
        column.setTableId(table.getTableId());
        column.setCreateBy(table.getCreateBy());
        // 设置java字段名
        column.setJavaField(StringUtils.toCamelCase(columnName));
        // 设置默认类型
        column.setJavaType(GeneratorConstants.TYPE_STRING);

        if (arraysContains(GeneratorConstants.COLUMNTYPE_STR, dataType)
                || arraysContains(GeneratorConstants.COLUMNTYPE_TEXT, dataType)) {
            // 字符串长度超过500设置为文本域
            Integer columnLength = getColumnLength(column.getColumnType());
            String htmlType = columnLength >= 500 || arraysContains(GeneratorConstants.COLUMNTYPE_TEXT, dataType)
                    ? GeneratorConstants.HTML_TEXTAREA
                    : GeneratorConstants.HTML_INPUT;
            column.setHtmlType(htmlType);
        } else if (arraysContains(GeneratorConstants.COLUMNTYPE_TIME, dataType)) {
            column.setJavaType(GeneratorConstants.TYPE_DATE);
            column.setHtmlType(GeneratorConstants.HTML_DATETIME);
        } else if (arraysContains(GeneratorConstants.COLUMNTYPE_NUMBER, dataType)) {
            column.setHtmlType(GeneratorConstants.HTML_INPUT);

            // 如果是浮点型 统一用BigDecimal
            String betweenStr = StringUtils.substringBetween(column.getColumnType(), PARENTHESES[0], PARENTHESES[1]);
            String[] str = StringUtils.split(betweenStr, COMMA);
            boolean isBigDecimal = str != null && str.length == 2 && Integer.parseInt(str[1]) > 0;
            if (isBigDecimal) {
                column.setJavaType(GeneratorConstants.TYPE_BIGDECIMAL);
            } else {
                boolean isInteger = str != null && str.length == 1 && Integer.parseInt(str[0]) <= 10;
                if (isInteger) {
                    column.setJavaType(GeneratorConstants.TYPE_INTEGER);
                } else {
                    // 长整形
                    column.setJavaType(GeneratorConstants.TYPE_LONG);
                }
            }
        }

        // 插入字段（默认所有字段都需要插入）
        column.setIsInsert(GeneratorConstants.REQUIRE);

        // 编辑字段
        if (!arraysContains(GeneratorConstants.COLUMNNAME_NOT_EDIT, columnName) && !column.isPk()) {
            column.setIsEdit(GeneratorConstants.REQUIRE);
        }
        // 列表字段
        if (!arraysContains(GeneratorConstants.COLUMNNAME_NOT_LIST, columnName) && !column.isPk()) {
            column.setIsList(GeneratorConstants.REQUIRE);
        }
        // 查询字段
        if (!arraysContains(GeneratorConstants.COLUMNNAME_NOT_QUERY, columnName) && !column.isPk()) {
            column.setIsQuery(GeneratorConstants.REQUIRE);
        }

        // 搜索字段类型
        if (StringUtils.endsWithIgnoreCase(columnName, ColumnSuffix.NAME)) {
            column.setQueryType(GeneratorConstants.QUERY_LIKE);
        }
        if (StringUtils.equals(column.getJavaType(), GeneratorConstants.TYPE_DATE)) {
            column.setQueryType(GeneratorConstants.QUERY_BETWEEN);
        }
        // 状态字段设置单选框
        if (StringUtils.endsWithIgnoreCase(columnName, ColumnSuffix.STATUS)) {
            column.setHtmlType(GeneratorConstants.HTML_RADIO);
        }
        // 类型&性别字段设置下拉框
        else if (StringUtils.endsWithIgnoreCase(columnName, ColumnSuffix.TYPE)
                || StringUtils.endsWithIgnoreCase(columnName, ColumnSuffix.SEX)) {
            column.setHtmlType(GeneratorConstants.HTML_SELECT);
        }
        // 图片字段设置图片上传控件
        else if (StringUtils.endsWithIgnoreCase(columnName, ColumnSuffix.IMAGE)) {
            column.setHtmlType(GeneratorConstants.HTML_IMAGE_UPLOAD);
        }
        // 文件字段设置文件上传控件
        else if (StringUtils.endsWithIgnoreCase(columnName, ColumnSuffix.FILE)) {
            column.setHtmlType(GeneratorConstants.HTML_FILE_UPLOAD);
        }
        // 内容字段设置富文本控件
        else if (StringUtils.endsWithIgnoreCase(columnName, ColumnSuffix.CONTENT)) {
            column.setHtmlType(GeneratorConstants.HTML_EDITOR);
        }
    }

    /**
     * 校验数组是否包含指定值
     * 
     * @param arr         数组
     * @param targetValue 值
     * @return 是否包含
     */
    public static boolean arraysContains(String[] arr, String targetValue) {
        return Arrays.asList(arr).contains(targetValue);
    }

    /**
     * 获取业务名
     * 
     * @param tableName 表名
     * @return 业务名
     */
    public static String getBusinessName(String tableName) {
        int lastIndex = tableName.lastIndexOf("_");
        int nameLength = tableName.length();
        String businessName = StringUtils.substring(tableName, lastIndex + 1, nameLength);
        return businessName;
    }

    /**
     * 表名转换成Java类名
     * 
     * @param tableName 表名称
     * @return 类名
     */
    public static String convertClassName(String tableName) {
        String tablePrefix = getTablePrefix(tableName);
        if (StringUtils.isNotEmpty(tablePrefix)) {
            String[] searchList = StringUtils.split(tablePrefix, COMMA);
            tableName = replaceFirst(tableName, searchList);
        }
        return StringUtils.convertToCamelCase(tableName);
    }

    /**
     * 批量替换前缀
     * 
     * @param replacementm 替换值
     * @param searchList   替换列表
     * @return
     */
    public static String replaceFirst(String replacementm, String[] searchList) {
        String text = replacementm;
        for (String searchString : searchList) {
            if (replacementm.startsWith(searchString)) {
                text = replacementm.replaceFirst(searchString, "");
                break;
            }
        }
        return text;
    }

    /**
     * 关键字替换
     * 
     * @param text 需要被替换的名字
     * @return 替换后的名字
     */
    public static String replaceText(String text) {
        return RegExUtils.replaceAll(text, "(?:表|记录)", "");
    }

    /**
     * 获取数据库类型字段
     * 
     * @param columnType 列类型
     * @return 截取后的列类型
     */
    public static String getDbType(String columnType) {
        if (StringUtils.indexOf(columnType, PARENTHESES[0]) > 0) {
            return StringUtils.substringBefore(columnType, PARENTHESES[0]);
        } else {
            return columnType;
        }
    }

    /**
     * 获取字段长度
     * 
     * @param columnType 列类型
     * @return 截取后的列类型
     */
    public static Integer getColumnLength(String columnType) {
        if (StringUtils.indexOf(columnType, PARENTHESES[0]) > 0) {
            String length = StringUtils.substringBetween(columnType, PARENTHESES[0], PARENTHESES[1]);
            return Integer.valueOf(length);
        } else {
            return 0;
        }
    }

    /**
     * 获取表名前缀
     * 
     * @author yilabao
     * @date 2021年1月27日
     * @param tableName
     * @return String
     */
    public static String getTablePrefix(String tableName) {
        int firstIndex = tableName.indexOf("_");
        if (firstIndex > 0) {
            return tableName.substring(0, firstIndex).toLowerCase();
        }
        return "";
    }

    /**
     * 获取模块名
     * 
     * @author yilabao
     * @date 2021年1月27日
     * @param tableName
     * @return String
     */
    public static String getModuleName(String tableName) {
        String tablePrefix = getTablePrefix(tableName);
        return StringUtils.defaultIfBlank(tablePrefix, tableName);
    }

}